package com.wu.gumomallproduct.product.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
import com.wu.common.constant.ProductConstant;
import com.wu.common.entity.product.*;
import com.wu.common.es.SkuEsModel;
import com.wu.common.to.SkuReductionTo;
import com.wu.common.to.SpuBoundTo;
import com.wu.common.utils.R;
import com.wu.gumomallproduct.product.dao.AttrDao;
import com.wu.gumomallproduct.product.service.*;
import com.wu.gumomallproduct.product.service.feign.CouponFeignService;
import com.wu.gumomallproduct.product.service.feign.SearchFeignService;
import com.wu.gumomallproduct.product.service.feign.WareFeignService;
import com.wu.common.vo.product.BaseAttrs;
import com.wu.common.vo.product.Images;
import com.wu.common.vo.product.Sku;
import com.wu.common.vo.product.SpuSaveVo;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.wu.common.utils.PageUtils;
import com.wu.common.utils.Query;

import com.wu.gumomallproduct.product.dao.SpuInfoDao;
import org.springframework.transaction.annotation.Transactional;


@Service("spuInfoService")
public class SpuInfoServiceImpl extends ServiceImpl<SpuInfoDao, SpuInfoEntity> implements SpuInfoService {

    @Autowired
    private SpuInfoDescService spuInfoDescService;
    @Autowired
    private CategoryService categoryService;
    @Autowired
    private WareFeignService wareFeignService;
    @Autowired
    private SearchFeignService searchFeignService;

    @Autowired
    private BrandService brandService;
    @Autowired
    private SkuSaleAttrValueService skuSaleAttrValueService;
    @Autowired
    private SkuImagesService skuImagesService;
    @Autowired
    private ProductAttrValueService productAttrValueService;
    @Autowired
    private SpuImagesService spuImagesService;
    @Autowired
    private SkuInfoService skuInfoService;
    @Autowired
    private AttrDao attrDao;
    @Autowired
    private CouponFeignService couponFeignService;

    @Override
    public PageUtils queryPage(Map<String, Object> params) {
        LambdaQueryWrapper<SpuInfoEntity> queryWrapper = new LambdaQueryWrapper<>();
        String key = params.get("key").toString();
        if (StringUtils.isNotEmpty(key)){
            queryWrapper.and(w->{
                w.eq(SpuInfoEntity::getId, key).or().like(SpuInfoEntity::getSpuName, key);
            });
        }
        String  catelogId = params.get("catelogId").toString();
        if (!catelogId.equals("0")){
            queryWrapper.eq(SpuInfoEntity::getCatalogId, catelogId);
        }
        String brandId = params.get("brandId").toString();
        if (!brandId.equals("0")){
            queryWrapper.eq(SpuInfoEntity::getBrandId, brandId);
        }
        Object status = params.get("status");
        if (ObjectUtils.isNotNull(status)){
            queryWrapper.eq(SpuInfoEntity::getPublishStatus, status);
        }
        IPage<SpuInfoEntity> page = this.page(
                new Query<SpuInfoEntity>().getPage(params),
                queryWrapper
        );
        return new PageUtils(page);
    }

    @Override
    @Transactional
    public void saveSpuSaveVo(SpuSaveVo spuSaveVo) {
        //1.保存基本属性  pms_spu_info
        SpuInfoEntity spuInfoEntity = new SpuInfoEntity();
        BeanUtils.copyProperties(spuSaveVo, spuInfoEntity);
        this.save(spuInfoEntity);
        //2.保存spu描述  pms_spu_desc
        SpuInfoDescEntity spuInfoDescEntity = new SpuInfoDescEntity(spuInfoEntity.getId(), String.join(",", spuSaveVo.getDecript()));
        spuInfoDescService.save(spuInfoDescEntity);
        //3.保存spu图片  pms_spu_images
        List<SpuImagesEntity> collect = spuSaveVo.getImages().stream().map(x -> {
            SpuImagesEntity spuImagesEntity = new SpuImagesEntity();
            spuImagesEntity.setSpuId(spuImagesEntity.getSpuId());
            spuImagesEntity.setImgUrl(x);
            return spuImagesEntity;
        }).collect(Collectors.toList());
        spuImagesService.saveBatch(collect);
        //4.保存spu基本属性  pms_product_attr_value
        List<BaseAttrs> baseAttrs = spuSaveVo.getBaseAttrs();
        List<ProductAttrValueEntity> productAttrValues = baseAttrs.stream().map(baseAttr -> {
            ProductAttrValueEntity productAttrValueEntity = new ProductAttrValueEntity();
            productAttrValueEntity.setSpuId(spuInfoEntity.getId());
            productAttrValueEntity.setAttrName(attrDao.selectById(baseAttr.getAttrId()).getAttrName());
            productAttrValueEntity.setAttrId(baseAttr.getAttrId());
            productAttrValueEntity.setAttrValue(baseAttr.getAttrValues());
            productAttrValueEntity.setQuickShow(baseAttr.getShowDesc());
            return productAttrValueEntity;
        }).collect(Collectors.toList());
        productAttrValueService.saveBatch(productAttrValues);
        //TODO 远程服务
        SpuBoundTo spuBoundTo = new SpuBoundTo();
        BeanUtils.copyProperties(spuSaveVo.getBounds(), spuBoundTo);
        spuBoundTo.setSpuId(spuInfoEntity.getId());
        R r = couponFeignService.saveSpuBounds(spuBoundTo);
        if (r.getCode() != 0){
            throw new RuntimeException("远程出错");
        }


        //5保存sku基本信息
        List<Sku> skus = spuSaveVo.getSkus();
        for (Sku sku : skus) {
            SkuInfoEntity skuInfoEntity = new SkuInfoEntity();
            skuInfoEntity.setSpuId(spuInfoEntity.getId());
            skuInfoEntity.setSkuDesc(String.join(",", sku.getDescar()));
            skuInfoEntity.setPrice(sku.getPrice());
            skuInfoEntity.setSkuName(sku.getSkuName());
            skuInfoEntity.setBrandId(spuInfoEntity.getBrandId());
            skuInfoEntity.setCatalogId(spuInfoEntity.getCatalogId());
            skuInfoEntity.setSaleCount(0L);
            List<Images> collect1 = sku.getImages().stream().filter(x -> x.getDefaultImg() == 1).collect(Collectors.toList());
            if (collect1 ==null || collect1.size()!=1){
                throw new RuntimeException("sku默认图片只能有一个");
            }
            skuInfoEntity.setSkuDefaultImg(collect1.get(0).getImgUrl());
            skuInfoEntity.setSkuSubtitle(sku.getSkuSubtitle());
            skuInfoEntity.setSkuTitle(sku.getSkuTitle());
            skuInfoService.save(skuInfoEntity);
            //6.保存sku图片信息
            List<SkuImagesEntity> skuImagesEntityList = sku.getImages().stream().filter(x-> StringUtils.isNotEmpty(x.getImgUrl())).map(images -> {
                SkuImagesEntity skuImagesEntity = new SkuImagesEntity();
                skuImagesEntity.setSkuId(skuInfoEntity.getSkuId());
                skuImagesEntity.setImgUrl(images.getImgUrl());
                skuImagesEntity.setDefaultImg(images.getDefaultImg());
                return skuImagesEntity;
            }).collect(Collectors.toList());
            skuImagesService.saveBatch(skuImagesEntityList);
            //7.保存sku销售属性
            List<SkuSaleAttrValueEntity> skuSaleAttrValueEntities = sku.getAttr().stream().map(attr -> {
                SkuSaleAttrValueEntity skuSaleAttrValue = new SkuSaleAttrValueEntity();
                skuSaleAttrValue.setSkuId(skuInfoEntity.getSkuId());
                skuSaleAttrValue.setAttrId(attr.getAttrId());
                skuSaleAttrValue.setAttrName(attr.getAttrName());
                skuSaleAttrValue.setAttrValue(attr.getAttrValue());
                return skuSaleAttrValue;
            }).collect(Collectors.toList());
            skuSaleAttrValueService.saveBatch(skuSaleAttrValueEntities);
            //8.
            SkuReductionTo skuReductionTo = new SkuReductionTo();
            BeanUtils.copyProperties(sku, skuReductionTo);
            skuReductionTo.setSkuId(skuInfoEntity.getSkuId());
            r = couponFeignService.skuReductionTo(skuReductionTo);
            if (r.getCode() != 0){
                throw new RuntimeException("远程出错");
            }

        }



    }



//private List<SkuEsModel.Attrs> attrs;
//
//    @Data
//    public static class Attrs {
//
//        private Long attrId;
//
//        private String attrName;
//
//        private String attrValue;
//
//    }

    @Override
    public void productUp(Long spuId) {
        List<SkuInfoEntity> list = skuInfoService.list(new LambdaQueryWrapper<SkuInfoEntity>().eq(SkuInfoEntity::getSpuId, spuId));

        R r = wareFeignService.productStatusUp(list.stream().map(x->x.getSpuId()).collect(Collectors.toList()));
        if (r.getCode().compareTo(0) != 0){
            throw new RuntimeException("获取库存出错");
        }
        Map<Long, Boolean> map = (Map<Long, Boolean>) r.get("data");

        List<com.wu.common.es.SkuEsModel.Attrs>  attrs = productAttrValueService.getAttrsBySpuId(spuId);
        List<SkuEsModel> collect = list.stream().map(skuInfoEntity -> {
            SkuEsModel skuEsModel = new SkuEsModel();
            BeanUtils.copyProperties(skuInfoEntity, skuEsModel);
            skuEsModel.setSkuPrice(skuInfoEntity.getPrice());
            skuEsModel.setSkuImg(skuInfoEntity.getSkuDefaultImg());
            skuEsModel.setHotScore(0L);
            skuEsModel.setHasStock(map.getOrDefault(skuEsModel.getSkuId(), false));
            if (skuEsModel.getBrandId() != null || skuEsModel.getBrandId().compareTo(0L) > 0) {
                BrandEntity brandEntity = brandService.getById(skuEsModel.getBrandId());
                skuEsModel.setBrandName(brandEntity.getName());
                skuEsModel.setBrandImg(brandEntity.getLogo());
            }
            if (skuEsModel.getCatalogId() != null || skuEsModel.getCatalogId().compareTo(0L) > 0) {
                CategoryEntity category = categoryService.getById(skuEsModel.getCatalogId());
                skuEsModel.setCatalogName(category.getName());
            }
            skuEsModel.setAttrs(attrs);
            return skuEsModel;
        }).collect(Collectors.toList());

        R result = searchFeignService.productStatusUp(collect);

        if (result.getCode() == 0) {
            //远程调用成功
            //TODO 6、修改当前spu的状态
            SpuInfoEntity spuInfoEntity = new SpuInfoEntity();
            this.baseMapper.updaSpuStatus(spuId, ProductConstant.ProductStatusEnum.SPU_UP.getCode());
        } else {
            //远程调用失败
            //TODO 7、重复调用？接口幂等性:重试机制
        }


    }

}